<template>
  <div class="sanfan-tablePage">
    <div class="table_btn">
      <div v-show="tableExportPrintingCurrent">
        <el-button @click="exportToExcel" size="mini" icon="el-icon-download">导出</el-button>
        <el-button v-print="'#printID'" size="mini" icon="el-icon-printer">打印</el-button>
      </div>
      <div v-show="tableExportPrinting">
        <el-button @click="exportToExcel" size="mini" icon="el-icon-download">导出本页</el-button>
        <el-button v-print="'#printID'" size="mini" icon="el-icon-printer">打印本页</el-button>
        <el-button @click="handleAllData('export')" size="mini" icon="el-icon-download">导出全部</el-button>
        <el-button @click="handleAllData('print')" size="mini" icon="el-icon-printer">打印全部</el-button>
        <el-button v-show="false" id="printBtn" v-print="'#printAllID'" size="mini" icon="el-icon-printer">打印全部
        </el-button>
      </div>
    </div>
    <div :id="tableID">
      <tr v-if="isTableTitle" style="display: block;">
        <th :colspan="tableTitleColspan" style="display: block;">
          <div style="font-size: 24px;font-weight: 400;color: #606266;text-align: center;padding:15px 0;">{{tableTitle}}
          </div>
        </th>
      </tr>
      <tr v-if="tableSubTitle" style="display: block;">
        <th :colspan="tableTitleColspan" style="display: block;">
          <div style="font-size: 14px;color: #606266;text-align: right;padding: 10px 20px;">{{tableSubTitle}}</div>
        </th>
      </tr>
      <el-table class="sanfan-table" :show-summary="showSummary" :border="border" :height="tableHeight"
        :max-height="tableMaxHeight" v-loading="loading" element-loading-text="数据加载中"
        element-loading-background="rgba(0, 0, 0, 0.7)" :data="tableData" :default-sort="tableSort"
        style="width: 100%;table-layout:fixed;" :span-method="objectSpanMethod" @cell-mouse-leave="cellMouseLeave"
        @cell-mouse-enter="cellMouseEnter" @cell-dblclick="handleTableDbEdit" @row-click="rowClick"
        :highlight-current-row="true" @selection-change="handleSelectionChange" @current-change="handleSelectionChange">
        <el-table-column v-if="isSelection" type="selection" width="55"></el-table-column>
        <el-table-column v-if="isIndex" type="index" width="60" label="序号" align="center" :index="indexMethod"
          :fixed="true"></el-table-column>
        <el-table-column v-for="(item,index) in tableHeader" :key="index" :prop="item.mark"
          :label="item.unit?item.name+'('+item.unit+')':item.name" :min-width="item.minWidth" :width="item.width"
          align="center" :show-overflow-tooltip="true" :fixed="item.fixed">
          <template slot-scope="scope">
            <span v-if="item.mark"
              :class="(scope.row[item.mark]!==null&&scope.row[item.mark]!==undefined?(scope.row[item.mark].value<scope.row[item.mark].min||scope.row[item.mark].value>scope.row[item.mark].max):false)?'red':(item.color?item.color[scope.row[item.marks]]:'')">{{scope.row[item.mark]!==null&&scope.row[item.mark]!==undefined?(scope.row[item.mark].value?scope.row[item.mark].value:(item.list?item.list[scope.row[item.mark]]:(item.showList?(item.showList[scope.row[item.marks]]?scope.row[item.mark]:'-'):(item.toFixedNum?scope.row[item.mark].toFixed(item.toFixedNum):scope.row[item.mark])))):''}}</span>
            <div v-else>
              <el-button v-for="(it,i) in tableOperation" :key="'font'+i"
                v-show="!it.icon&&(it.list?it.list[scope.row[it.mark]]:it.name)"
                @click="handleClick(scope.row,it.mark,scope.$index)" size="mini" class="themeBtn"
                :disabled="it.disabled&&scope.row[it.conditionMark]==it.conditionNum">
                {{it.list?it.list[scope.row[it.mark]]:it.name}}</el-button>
              <el-button :title="it.name" v-for="(it,i) in tableOperation" :key="'icon'+i"
                v-show="it.icon&&(it.list?it.list[scope.row[it.mark]]:it.mark)"
                :icon="'el-icon-'+(it.list?it.list[scope.row[it.mark]]:it.mark)" circle
                @click="handleClick(scope.row,it.mark,scope.$index)" size="mini" class="themeBtn"
                :disabled="it.disabled&&scope.row[it.conditionMark]==it.conditionNum"></el-button>
            </div>
          </template>
        </el-table-column>
      </el-table>
    </div>
    <el-pagination v-show="tablePagination.show" @size-change="handleSizeChange" @current-change="handleCurrentChange"
      :current-page="tablePagination.current" :page-sizes="pageSizes" :page-size="tablePagination.size" background
      layout="total, sizes, prev, pager, next, jumper" :total="tablePagination.total"></el-pagination>
    <div id="printID">
      <div style="font-size: 20px;text-align: center;padding: 0 0 10px;">{{tableTitle}}</div>
      <p style="text-align: right;padding:0 20px 5px 0">
        <span>{{tableSubTitle}}</span>
      </p>
      <table style="width: 100%;text-align: center;border-collapse: collapse;">
        <thead style="display: table-header-group;">
          <tr>
            <th v-if="isIndex">序号</th>
            <template v-for="(item,index) in tableHeader">
              <th :key="index" v-if="item.name!= '操作'" :width="item.minWidth||item.width">
                {{item.unit?item.name+'('+item.unit+')':item.name}}</th>
            </template>
          </tr>
        </thead>
        <tbody>
          <tr v-for="(Item,Index) in tableData" :key="Index">
            <td v-if="isIndex">{{Index+1}}</td>
            <td v-for="(item,index) in tableHeader" :key="index">
              {{Item[item.mark]!==null&&Item[item.mark]!==undefined?(Item[item.mark].value?Item[item.mark].value:(item.list?item.list[Item[item.mark]]:(item.showList?(item.showList[Item[item.marks]]?Item[item.mark]:'-'):(item.toFixedNum?Item[item.mark].toFixed(item.toFixedNum):Item[item.mark])))):''}}
            </td>
          </tr>
        </tbody>
        <!-- <tfoot v-if="tableTitleColspan">
          <tr>
            <td :colspan="tableTitleColspan">打印时间：{{printTime}}</td>
          </tr>
        </tfoot>-->
      </table>
    </div>
    <div id="printAllID">
      <div style="font-size: 20px;text-align: center;padding: 0 0 10px;">{{tableTitle}}</div>
      <p style="text-align: right;padding:0 20px 5px 0">
        <span>{{tableSubTitle}}</span>
      </p>
      <table style="width: 100%;text-align: center;border-collapse: collapse;">
        <thead style="display: table-header-group;">
          <tr>
            <th v-if="isIndex">序号</th>
            <template v-for="(item,index) in tableHeader">
              <th :key="index" v-if="item.name!= '操作'" :width="item.minWidth||item.width">
                {{item.unit?item.name+'('+item.unit+')':item.name}}</th>
            </template>
          </tr>
        </thead>
        <tbody>
          <tr v-for="(Item,Index) in tableAllData" :key="Index">
            <td v-if="isIndex">{{Index+1}}</td>
            <td v-for="(item,index) in tableHeader" :key="index">
              {{Item[item.mark]!==null&&Item[item.mark]!==undefined?(Item[item.mark].value?Item[item.mark].value:(item.list?item.list[Item[item.mark]]:(item.showList?(item.showList[Item[item.marks]]?Item[item.mark]:'-'):(item.toFixedNum?Item[item.mark].toFixed(item.toFixedNum):Item[item.mark])))):''}}
            </td>
          </tr>
        </tbody>
      </table>
    </div>
  </div>
</template>

<script>
  import FileSaver from "file-saver";
  import XLSX from "xlsx";

  export default {
    name: "PagesTable",
    props: {
      tableExportPrintingCurrent: Boolean, //导出打印当前页
      tableExportPrinting: Boolean,
      tableTitleColspan: Number,
      tableID: String,
      isTableTitle: Boolean,
      tableTitle: String,
      tableSubTitle: String,
      showSummary: Boolean,
      border: Boolean,
      tableHeight: String,
      tableMaxHeight: String,
      loading: Boolean,
      isIndex: Boolean,
      isSelection: Boolean,
      tableData: Array,
      tableHeader: Array,
      tableOperation: Array,
      tableSort: Object,
      tablePagination: Object,
      tableSpanMethod: Object,
      tableSpan: Object
    },
    data() {
      return {
        tableAllData: [],
        pageSizes: [10, 20, 50, 100],
        printTime: new Date().format("yyyy-MM-dd"),
        spanArr: [],
        indexArr: []
      };
    },
    watch: {
      "tablePagination.total": "handlePageSizes",
      tableData: "handleSpanArr"
    },
    methods: {
      handlePageSizes() {
        this.pageSizes = [10, 20, 50, 100];
        if (this.tablePagination.total > 100) {
          this.pageSizes.push(this.tablePagination.total);
        }
      },
      handleSpanArr() {
        if (this.tableSpan) {
          const data = this.tableData;
          const mark = this.tableSpan.mark;
          this.spanArr = [];
          this.indexArr = [];
          let index = 0
          for (var i = 0; i < data.length; i++) {
            this.tableData[i].rowIndex = i;
            if (i === 0) {
              index++
              this.spanArr.push(1);
              this.indexArr.push(index);
              this.pos = 0;
            } else {
              // 判断当前元素与上一个元素是否相同,因合并第一个所以[0]
              if (data[i][mark] === data[i - 1][mark]) {
                this.spanArr[this.pos] += 1;
                this.spanArr.push(0);
                this.indexArr.push(0);
              } else {
                index++
                this.spanArr.push(1);
                this.indexArr.push(index);
                this.pos = i;
              }
            }
          }
        }
      },
      objectSpanMethod({
        row,
        column,
        rowIndex,
        columnIndex
      }) {
        const self = this;
        if (
          self.tableSpanMethod &&
          rowIndex === self.tableSpanMethod.tableRowIndex
        ) {
          for (let i in self.tableSpanMethod.tableColIndex) {
            if (columnIndex === self.tableSpanMethod.tableColIndex[i]) {
              return {
                rowspan: 1,
                colspan: 1
              };
            } else if (
              columnIndex === Number(self.tableSpanMethod.tableColIndex[i] + 1)
            ) {
              return {
                rowspan: 1,
                colspan: self.tableSpanMethod.tablecolspan
              };
            }
          }
          return {
            rowspan: 0,
            colspan: 0
          };
        }
        //合并行元素
        if (this.tableSpan) {
          if (this.tableSpan.colsIndex.includes(columnIndex)) {
            const _row = this.spanArr[rowIndex];
            const _col = _row > 0 ? 1 : 0;
            return {
              rowspan: _row,
              colspan: _col
            };
          }
        }
      },
      indexMethod(index) {
        if (this.tableSpan) {
          return this.indexArr[index];
        } else {
          return index + 1;
        }
      },
      //当单元格 hover 进入时会触发该事件
      cellMouseEnter(row, column, cell, event) {
        if (this.spanArr[row.rowIndex] == 0) {
          //向上查找它的合并头行,给合并头加样式
          for (let index = row.rowIndex; index >= 0; index--) {
            if (this.spanArr[index] > 0) {
              $("#" + this.tableID + " .sanfan-table .el-table__body-wrapper tbody tr")
                .eq(index)
                .addClass("trCurrent");
              //固定列添加类名
              $("#" + this.tableID + " .sanfan-table .el-table__fixed tbody tr")
                .eq(index)
                .addClass("trCurrent");
              $("#" + this.tableID + " .sanfan-table .el-table__fixed-right tbody tr")
                .eq(index)
                .addClass("trCurrent");
              return false;
            }
          }
        }
      },
      //当单元格 hover 退出时会触发该事件
      cellMouseLeave(row, column, cell, event) {
        $("tbody tr").removeClass("trCurrent");
      },
      //当某一行被点击时会触发该事件
      rowClick(row, column, event) {
        $("tbody tr td").removeClass("tdCurrent");
        if (this.spanArr[row.rowIndex] == 0) {
          //向上查找它的合并头行,给合并头加样式
          for (let index = row.rowIndex; index >= 0; index--) {
            if (this.spanArr[index] > 0) {
              $("#" + this.tableID + " .sanfan-table .el-table__body-wrapper tbody tr")
                .eq(index)
                .children("[rowspan!='1']")
                .addClass("tdCurrent");
              //固定列添加类名
              $("#" + this.tableID + " .sanfan-table .el-table__fixed tbody tr")
                .eq(index)
                .children("[rowspan!='1']")
                .addClass("tdCurrent");
              $("#" + this.tableID + " .sanfan-table .el-table__fixed-right tbody tr")
                .eq(index)
                .children("[rowspan!='1']")
                .addClass("tdCurrent");
              return false;
            }
          }
        }
      },
      handleSelectionChange(val) {
        this.$emit("selectionChange", val);
      },
      handleTableDbEdit(row, column, cell, event) {
        this.$emit("tableDbEdit", row, column, cell, event);
      },
      handleClick(row, mark, index) {
        this.$emit("pageOperation", row, mark, index);
      },
      handleSizeChange(val) {
        this.$emit("pageSize", val);
      },
      handleCurrentChange(val) {
        this.$emit("currentPage", val);
      },
      exportToExcel() {
        const self = this;
        //  判断要导出的节点中是否有fixed的表格，如果有，重组表格
        let fix = document.querySelector(".el-table__fixed");
        let fixRight = document.querySelector(".el-table__fixed-right");
        let et;
        if (fix || fixRight) {
          //重组表格
          let newDiv = document.createElement("div");
          let headerContent = document
            .getElementById(self.tableID)
            .querySelector(".sanfan-table .el-table__header-wrapper")
            .cloneNode(true);
          let bodyContent = document
            .getElementById(self.tableID)
            .querySelector(".sanfan-table .el-table__body-wrapper")
            .cloneNode(true);

          //移除操作列
          var table1 = headerContent.querySelector("table");
          var table2 = bodyContent.querySelector("table");
          var index = "";
          var cells = table1.rows[0].cells;
          for (let i = 0; i < cells.length; i++) {
            const element = cells[i];
            if (element.textContent == "操作") {
              index = i;
              break;
            }
          }
          var len = table2.rows.length;
          if (index != "") {
            table1.rows[0].deleteCell(index);
            for (var i = 0; i < len; i++) {
              if (table2.rows[i].children[index]) {
                table2.rows[i].deleteCell(index);
              }
            }
          }

          newDiv.appendChild(headerContent);
          newDiv.appendChild(bodyContent);
          et = XLSX.utils.table_to_book(newDiv, {
            raw: true
          });
        } else {
          et = XLSX.utils.table_to_book(document.getElementById(self.tableID), {
            raw: true
          });
        }
        let etout = XLSX.write(et, {
          bookType: "xlsx",
          bookSST: true,
          type: "array"
        });
        try {
          FileSaver.saveAs(
            new Blob([etout], {
              type: "application/octet-stream"
            }),
            self.tableTitle + ".xlsx"
          );
        } catch (e) {
          console.log(e, etout);
        }
        return etout;
      },
      handleAllData(text) {
        //获取全部数据
        self.tableAllData = []
        this.$emit("getTableAllData", text);
      },
      exportAllToExcel(data) {
        const self = this;
        self.tableAllData = data
        setTimeout(function () {
          let et = XLSX.utils.table_to_book(document.getElementById('printAllID'), {
            raw: true
          });
          let etout = XLSX.write(et, {
            bookType: "xlsx",
            bookSST: true,
            type: "array"
          });
          try {
            FileSaver.saveAs(
              new Blob([etout], {
                type: "application/octet-stream"
              }),
              self.tableTitle + ".xlsx"
            );
          } catch (e) {
            console.log(e, etout);
          }
          return etout;
        }, 1000)
      },
      printAllData(data) {
        this.tableAllData = data
        $('#printBtn').click()
      }
    }
  };
</script>

<style lang="scss">
  .el-table td {
    height: 30px;
  }

  .sanfan-table.el-table .el-input__inner {
    padding: 0 5px;
    text-align: center;
  }

  .trCurrent td[rowspan="1"] {
    background: #fff;
  }

  .trCurrent td {
    background: #f5f7fa;
  }

  .tdCurrent {
    background: #ecf5ff;
  }

  .red {
    color: #f56c6c;
  }

  .green {
    color: #67c23a;
  }

  .grey {
    color: #909399;
  }

  .el-pagination {
    text-align: right;
    padding: 12px 0;
  }

  #printID,
  #printAllID {
    display: none;
    padding: 0 20px;

    thead th {
      padding: 8px 0;
      text-align: center;
      border: 1px solid #606266;
    }

    tbody td {
      padding: 5px 0;
      border: 1px solid #606266;
    }

    tfoot td {
      padding: 8px 0;
      text-align: right;
      padding-right: 20px;
    }
  }

  @media print {

    #printID,
    #printAllID {
      display: block;
    }
  }
</style>